﻿using Framework.Components;
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Security.Principal;
using System.Text;
using System.Threading.Tasks;

namespace Framework.Utils
{
    /// <summary>
    /// CMD调用工具
    /// </summary>
    public static class CmdUtils
    {

        ///// <summary>
        ///// 管理员运行CMd(可以以管理员身份运行, 但是无法传入函数)
        ///// </summary>
        //public static void ExecuteByAdministrator(string cmdStr)
        //{
        //    // 创建启动对象
        //    var startInfo = new System.Diagnostics.ProcessStartInfo("cmd.exe");
        //    startInfo.Arguments = cmdStr + "&exit";
        //    startInfo.UseShellExecute = false;
        //    startInfo.WorkingDirectory = Environment.CurrentDirectory;
        //    startInfo.CreateNoWindow = false;          //不显示程序窗口

        //    //设置启动动作,确保以管理员身份运行
        //    startInfo.Verb = "runas";
        //    try
        //    {
        //        var process = Process.Start(startInfo);
        //        process.StandardInput.WriteLine(cmdStr);
        //        process.StandardInput.Flush();

        //        // 等待结束
        //        process.WaitForExit();
        //        process.Close();
        //    }
        //    catch(Exception e)
        //    {
        //        Log.Error("执行CMD错误! " + cmdStr, e);
        //    }
        //}


        /// <summary>
        /// 生成指令行(多个字符串合并)
        /// </summary>
        public static string CreateCmdLine(string[] args)
        {
            var strBdr = new StringBuilder();
            foreach (string cmdArg in args)
            {
                strBdr.Append(cmdArg).Append(" ");
            }
            return strBdr.ToString();
        }

        /// <summary>
        /// 启动程序
        /// </summary>
        public static Process StartProcess(string name, string args, string[] inputs = null, string path = null)
        {
            // 初始化路径
            if (string.IsNullOrEmpty(path))
            {
                path = Path.GetDirectoryName(name);
                // 没有路径, 改成程序路径
                if (string.IsNullOrEmpty(path))
                {
                    path = Environment.CurrentDirectory;    // 程序路径
                }
            }

            //获得当前登录的Windows用户标示
            // var identity = System.Security.Principal.WindowsIdentity.GetCurrent();
            // var principal = new System.Security.Principal.WindowsPrincipal(identity);

            // 参数设置
            ProcessStartInfo processInfo = new ProcessStartInfo(name);
            processInfo.Arguments = args;
            processInfo.WorkingDirectory = path;
            processInfo.UseShellExecute = false;        //是否使用操作系统shell启动
            processInfo.CreateNoWindow = true;          //不显示程序窗口
            processInfo.RedirectStandardError = true;   //由调用程序获取错误信息
            processInfo.RedirectStandardOutput = true;  //由调用程序获取输出信息
            processInfo.RedirectStandardInput = true;   //接受来自调用程序的输入信息
            processInfo.Verb = "runas"; //设置启动动作,确保以管理员身份运行

            // 启动程序
            Process process = Process.Start(processInfo);
            if(inputs != null)
            {
                // 遍历输入
                foreach(string input in inputs)
                {
                    process.StandardInput.WriteLine(input);
                }
            }
            process.StandardInput.WriteLine("exit");
            process.StandardInput.Flush();

            return process;
        }

        /// <summary>
        /// 等待程序结束, 获取内容
        /// </summary>
        public static string WaitProcess(Process process)
        {
            process.StandardInput.Close(); // 关闭输入

            // 等待输出
            string output = process.StandardOutput.ReadToEnd();
            string error = process.StandardError.ReadToEnd();
            process.WaitForExit();
            process.Close();

            // 安全终止
            try
            {
                process.Kill(); //强制终止
            }
            catch(Exception )
            {
            }

            // 整理输出
            var strBdr = new StringBuilder();
            if (!string.IsNullOrEmpty(output))
            {
                strBdr.Append(output);
            }
            if (!string.IsNullOrEmpty(error))
            {
                strBdr.Append("\n");
                strBdr.Append(error);
            }
            return strBdr.ToString();
        }


        /// <summary>
        /// 执行命令
        /// </summary>
        /// <param name="name">命令名</param>
        /// <param name="args">命令参数</param>
        /// <param name="path">调用目录</param>
        public static string Execute(string name, string args, string[] inputs = null, string path = null)
        {
            // 启动程序
            var process = StartProcess(name, args, inputs, path);
            return WaitProcess(process);
        }

#if NETCOREAPP2_0 || NETCOREAPP1_0 || NETCOREAPP1_1
        // .net core 代码
#else

        /// <summary>
        /// 判断当前程序是否是管理员运行
        /// </summary>
        public static bool IsAdministrator()
        {
            try
            {
                var identity = WindowsIdentity.GetCurrent();
                var principal = new WindowsPrincipal(identity);
                return principal.IsInRole(WindowsBuiltInRole.Administrator);
            }
            catch
            {
                return false;
            }
        }
#endif

    }
}
